import axios from "axios";
import { userInfo } from "@/stores/userinfo";
// 添加instence导入，用于重试原始请求
import instence from "./axiosConfig";

// 创建完全独立的axios实例，用于刷新令牌
// 为什么需要独立实例？避免与主实例的拦截器冲突，确保绝对纯净的请求环境
const refreshInstance = axios.create({
  timeout: 5000,
  headers: {
    "Content-Type": "application/json",
  },
});

// 存储等待令牌刷新的请求队列
let pendingRequests: Array<() => Promise<any>> = [];
// 令牌刷新状态标志
let isRefreshing = false;

/**
 * 处理等待中的请求
 * @param success - 是否刷新成功
 * @param token - 新的访问令牌
 */
const processPendingRequests = (success: boolean, token?: string) => {
  pendingRequests.forEach(callback => {
    if (success && token) {
      callback();
    } else {
      callback().catch(err => Promise.reject(err));
    }
  });
  pendingRequests = [];
};

/**
 * 刷新访问令牌
 * @returns 新的访问令牌
 */
export const refreshAuthToken = async (): Promise<string> => {
  const userStore = userInfo();
  const refreshToken = userStore.getRefreshToken;

  if (!refreshToken) {
    throw new Error("没有找到刷新令牌");
  }

  try {
    console.log("[authService] 开始刷新令牌流程");
    const response = await refreshInstance.post(
      `${import.meta.env.VITE_API_URL}/refreshToken`,
      { refreshToken },
      {
        // 明确不携带任何认证头
        headers: { Authorization: undefined }
      }
    );

    if (response.data.code !== 200 || !response.data.data?.accessToken) {
      throw new Error(`刷新令牌失败: ${response.data.msg || '未知错误'}`);
    }

    const { accessToken, refreshToken: newRefreshToken } = response.data.data;

    // 更新存储的令牌
    userStore.userInfo.accessToken = accessToken;
    if (newRefreshToken) {
      userStore.userInfo.refreshToken = newRefreshToken;
    }

    // 同步更新本地存储
    const storage = localStorage.getItem('rememberMe') === 'true' ? localStorage : sessionStorage;
    storage.setItem('accessToken', accessToken);
    if (newRefreshToken) {
      storage.setItem('refreshToken', newRefreshToken);
    }

    console.log("[authService] 令牌刷新成功");
    return accessToken;
  } catch (error) {
    console.error("[authService] 令牌刷新失败:", error);
    // 刷新失败时登出用户
    userStore.logout();
    throw error;
  }
};

/**
 * 获取当前有效的访问令牌
 * 如果令牌过期，会自动刷新
 * @returns 有效的访问令牌
 */
export const getValidAccessToken = async (): Promise<string> => {
  const userStore = userInfo();
  const currentToken = userStore.getToken;

  // 如果没有令牌，直接抛出错误
  if (!currentToken) {
    throw new Error("未登录或令牌已过期");
  }

  // 如果正在刷新令牌，等待刷新完成
  if (isRefreshing) {
    return new Promise((resolve, reject) => {
      pendingRequests.push(() => {
        const newToken = userStore.getToken;
        return newToken ? resolve(newToken) : reject(new Error("令牌刷新失败"));
      });
    });
  }

  // 这里可以添加令牌过期时间检查逻辑
  // 简化处理：直接返回当前令牌，由服务器判断是否过期
  return currentToken;
};

/**
 * 请求拦截器：添加认证令牌
 */
export const requestInterceptor = async (config: any) => {
  // 不需要认证的接口列表
  const publicPaths = ['/login', '/refreshToken','/logout','/register/add','/sms/verify-sms-code','/register/checkContact','/sms/send-sms-code','/register/checkUsername','/alluser/textMessageLogin'
      ,'/userStatistics/last7days', '/userStatistics/scoreLevel','/ctfcontest/searchByUserName'];
  const isPublicPath = publicPaths.some(path => config.url?.includes(path));

  console.log("[authService] 请求URL:", config.url, "是否公开:", isPublicPath);

  if (!isPublicPath) {
    try {
      // 获取有效的访问令牌
      const token = await getValidAccessToken();
      config.headers["Authorization"] = token;
      console.log("[authService] 添加Authorization头:", token.substring(0, 10) + "...");
    } catch (error) {
      console.error("[authService] 获取令牌失败:", error);
      throw error;
    }
  } else {
    // 公开接口，确保不携带认证头
    delete config.headers["Authorization"];
    console.log("[authService] 公开接口，已移除Authorization头");
  }

  return config;
};

/**
 * 响应拦截器：处理令牌过期
 */
export const responseInterceptor = async (error: any) => {
  console.error("[authService] 响应拦截器捕获到错误:", error, error?.config);
  const originalRequest = error.config;

  // 修改：同时检查HTTP状态码和业务状态码
  const isAuthError = 
    error.response?.status === 401 || 
    (error.response?.status === 200 && error.response?.data?.code === 401);

  // 如果不是认证错误或已经重试过，直接返回错误
  if (
    !error.response || 
    !isAuthError ||  // 使用新的认证错误判断
    originalRequest._retry ||
    originalRequest.url?.includes('/refreshToken')
  ) {
    console.log("[authService] 非令牌过期错误，状态码:", error.response?.status, "业务码:", error.response?.data?.code);
    return Promise.reject(error);
  }

  // 标记请求为已重试
  originalRequest._retry = true;

  try {
    // 开始刷新令牌
    isRefreshing = true;
    const newToken = await refreshAuthToken();

    // 刷新成功，处理等待的请求
    processPendingRequests(true, newToken);

    // 重试原始请求 - 修改：使用instence而非全局axios
    // 为什么使用instence？确保使用应用的axios实例和其配置
    originalRequest.headers["Authorization"] = newToken;
    return instence(originalRequest);
  } catch (refreshError) {
    // 刷新失败，拒绝所有等待的请求
    processPendingRequests(false);
    return Promise.reject(refreshError);
  } finally {
    isRefreshing = false;
  }
};